﻿using Com.FirstSolver.Splash;
using System;
using System.Collections;
using System.Collections.Generic;
using System.Data;
using System.Net;
using System.Text;

namespace SocketLib
{
    public class TCPserver
    {


        /// <summary>
        /// 设备通信字符集代码页为简体中文
        /// </summary>           
        private const int DeviceCodePage = 936;

        /// <summary>
        /// 服务器是否已运行
        /// </summary>
        private bool IsServerRunning = false;

        /// <summary>
        /// 心跳包接收服务器
        /// </summary>
        private TcpListenerPlus TcpServer = null;
        private bool jiam = false;
        private bool isphoto = false;

        public bool Start(string Ips = "*", int port = 9920)
        {
            if (!IsServerRunning)
            {
                try
                {
                    TcpServer = new TcpListenerPlus(IPAddress.Parse(Ips), port, jiam);
                    TcpServer.OnServerTaskRequest += OnServerTaskProcess;

                    FileOpetation.SaveRecord(string.Format(@"当前记录时间：{0},TCP 状况：{1}", DateTime.Now, "TCP 开启"));
                    // 启动侦听
                    TcpServer.StartListenThread(null, 0, 10 * 60 * 1000);
                    IsServerRunning = true;
                }
                catch (Exception ex)
                {

                    FileOpetation.SaveRecord(string.Format(@"当前记录时间：{0},TCP 状况：{1}", DateTime.Now, ex.Message));
                    IsServerRunning = false;
                }

            }
            return IsServerRunning;
        }
        // 接收数据处理程序
        private void OnServerTaskProcess(object sender, EventArgs e)
        {
            NetworkStreamPlus Stream = (NetworkStreamPlus)sender;

            string SerialNumber = "";    // 设备序列号
            string commad = "", xcmd = "", st = "";

            while (true)
            {
                try
                {

                    string Answer;
                    Stream.Read(out Answer, DeviceCodePage);

                    // 显示接收字符串
#if DEBUG
                    FileOpetation.SaveRecord(string.Format(@"：{0},TCP 状况：{1}", DateTime.Now, Answer));
#endif
                    if (Answer.StartsWith("PostRecord"))
                    {
                        // 提取序列号并保存
                        SerialNumber = FaceId_Item.GetKeyValue(Answer, "sn");
                        if (dao.SetOnline(SerialNumber) > 0)
                        {
                            // 答复已准备好接收考勤记录
                            if (isphoto)
                            {   // 上传照片
                                Stream.Write("Return(result=\"success\" postphoto=\"true\")", DeviceCodePage);
                            }
                            else
                            {   // 不上传照片
                                Stream.Write("Return(result=\"success\" postphoto=\"false\")", DeviceCodePage);
                            }
                        }
                        else
                        {
                            Stream.Write("Return(result =\"failed\")", DeviceCodePage);
                            break;
                        }
                    }
                    else if (Answer.StartsWith("Record"))
                    {   // 读取考勤记录

                        if (dao.insertlog(Answer, SerialNumber))
                        {
                            Stream.Write("Return(result=\"success\")", DeviceCodePage);   // 答复数据接收成功
                        }
                        else
                        {
                            Stream.Write("Return(result=\"failed\")", DeviceCodePage);
                        }

                    }
                    else if (Answer.StartsWith("PostEmployee"))
                    {   // 准备上传人员
                        SerialNumber = FaceId_Item.GetKeyValue(Answer, "sn");
                        Stream.Write("Return(result=\"success\")", DeviceCodePage);
                    }
                    else if (Answer.StartsWith("Employee"))
                    {   // 接收人员数据

                        dao.UpEmployee(Answer, SerialNumber);

                        Stream.Write("Return(result=\"success\")", DeviceCodePage);   // 答复数据接收成功
                        SendCMD(Stream, SerialNumber, out commad, out xcmd, out st);

                    }
                    else if (Answer.StartsWith("GetRequest"))
                    {   // 下发命令

                        SerialNumber = FaceId_Item.GetKeyValue(Answer, "sn");

                        string text = dao.Getcommond(SerialNumber, out st, out commad, out xcmd);
                        if (!string.IsNullOrEmpty(text))
                        {

                            Stream.Write(text, DeviceCodePage);
                        }
                        else
                        {
                            commad = "GetDeviceInfo()";
                            Stream.Write(commad, DeviceCodePage);
                        }

                    }
                    else if (Answer.StartsWith("Return(result=\"success\""))
                    {
                        if (!string.IsNullOrEmpty(xcmd))
                        {
                            if (commad == xcmd)
                            {
                                if (st != "")
                                {
                                    MySqlHelper.ExecuteSql("update lxb_command set isok=1, status=1 where id=" + st);
                                    st = "";

                                }
                            }
                        }
                        if (commad == "GetDeviceInfo()")
                        {
                            dao.SetInfo(Answer, SerialNumber);

                        }
                        if (commad.StartsWith("GetRecord("))
                        {
                            dao.batchlogs(Answer);
                        }
                        if (commad.StartsWith("GetEmployee("))
                        {
                            dao.UpEmployee(Answer, SerialNumber);
                        }

                        if (commad.StartsWith("GetEmployeeID()"))
                        {

                            ArrayList ids = RegexHelper.getAttrs(Answer, "id");
                            List<String> ls = new List<string>();

                            foreach (var item in ids)
                            {
                                ls.Add(String.Format("insert into lxb_command (sn,text) values('{0}','GetEmployee(id=\"{1}\")')", SerialNumber, item));
                            }
                            if (ls.Count > 0)
                            {
                                MySqlHelper.ExecuteSqlTran(ls);
                            }

                        }
                        SendCMD(Stream, SerialNumber, out commad, out xcmd, out st);

                    }
                    else if (Answer.StartsWith("Return(result=\"fail"))
                    {
                        FileOpetation.SaveRecord(string.Format(@"时间：{0}TCP 状况：{1}", DateTime.Now, Answer));

                        if (!string.IsNullOrEmpty(xcmd))
                        {
                            string res = FaceId_Item.GetKeyValue(Answer, "reason");
                            if (res == null) {
                                Answer = gbk_utf8(Answer);
                                res = Answer.Substring(Answer.IndexOf("reason")+6);
                            }

                            if (commad == xcmd)
                            {
                                MySqlHelper.ExecuteSql("update lxb_command set resion='" + res + "', isok=0, status=1 where id=" + st);
                                st = "";
                            }
                        }
                        SendCMD(Stream, SerialNumber, out commad, out xcmd, out st);
                    }
                    else if (Answer.StartsWith("Quit"))
                    {   // 连接断开
                        break;
                    }

                }
                catch (System.Net.Sockets.SocketException)
                {   // 套接字关闭                    
                    break;
                }
                catch (System.IO.IOException)
                {   // 套接字关闭
                    break;
                }
                catch (System.ObjectDisposedException)
                {   // 套接字关闭
                    break;
                }
                catch (Exception ex)
                {
                    string ErrorMessage = "错误信息：" + ex.GetType().Name;

                    FileOpetation.SaveRecord(string.Format(@"{0},TCP 服务：{1}", DateTime.Now, ex.StackTrace + ex.Message));
                }
            }
        }
        /*
         
             发送一个命令
             */
        private static void SendCMD(NetworkStreamPlus Stream, string SerialNumber, out string commad, out string xcmd, out string st)
        {
            string text = dao.Getcommond(SerialNumber, out st, out commad, out xcmd);
            if (!string.IsNullOrEmpty(text))
            {
                Stream.Write(text, DeviceCodePage);
            }
        }

        public static string gbk_utf8(string text)
        {
            byte[] bytes = Encoding.GetEncoding(936).GetBytes(text);//将字符串转成ascii编码的字节数组，这里的bytes数组，长度为4，分别对应于abcd的ascii码97、98、99、100  
            return Encoding.GetEncoding(65001).GetString(bytes);//将字节数组转回为字符串
        }

        public void close()
        {
            if (TcpServer != null)
            {
                TcpServer.Stop();
                TcpServer = null;



            }

            IsServerRunning = false;
        }


    }
}
